<!--
 * @Author: your name
 * @Date: 2022-03-15 14:10:54
 * @LastEditTime: 2022-03-16 11:41:33
 * @LastEditors: Please set LastEditors
 * @Description: 打开koroFileHeader查看配置 进行设置: https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
 * @FilePath: \geyao\geyao\手写call220315.html
-->
<!DOCTYPE html>
<html lang="en">
	<head>
		<meta charset="UTF-8" />
		<meta http-equiv="X-UA-Compatible" content="IE=edge" />
		<meta name="viewport" content="width=device-width, initial-scale=1.0" />
		<title>手写call</title>
	</head>
	<body>
		<script>
			Function.prototype.mycall = function (obj) {
				//判断是否为null或者undefined,如果是则默认window;如果传递的参数不是对象用Object转为对象
				obj = obj ? Object(obj) : window
				var args = []

				//注意此处for循环的i是从1开始，因为第1个参数是obj
				for (var i = 1, len = arguments.length; i < len; i++) {
					args.push('arguments' + '[' + i + ']')
				}
				console.log(args, 'args') //[ "arguments[1]", "arguments[2]", "arguments[3]" ]
				//最重要的一步！说明了两个问题：1.mycall内部的this是指向调用者fn函数（对象的）；2.Obj.func就是fn函数，
				// obj对象调用了fn函数，因此fn函数内部的this指向obj
				console.log(this, 'this') //function fn(a, b, c)
				obj.fn = this
				// console.log(obj.fn(args),"obj.fn")
				// console.log(eval("obj.fn("+args+")"),"eval")
				var result = eval('obj.fn(' + args + ')')
				delete obj.fn
				console.log(result, 'result') // 我的老婆是geyao
				return result
			}
			var name = 'fangfang'
			var obj = {
				name: 'geyao',
			}

			function fn(a, b, c) {
				console.log(a + b + c + this.name)
				return a + b + c + this.name
			}
			fn.mycall(obj, '我的', '老婆', '是') // 我的老婆是geyao
		</script>
	</body>
</html>
